package com.wechatapp.mengyao.poetry.biz;

import com.fasterxml.jackson.databind.ObjectMapper;
import lombok.Data;
import lombok.extern.slf4j.Slf4j;
import net.coobird.thumbnailator.Thumbnails;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.http.*;
import org.springframework.http.client.HttpComponentsClientHttpRequestFactory;
import org.springframework.stereotype.Service;
import org.springframework.web.client.RestTemplate;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.net.URLDecoder;
import java.util.Base64;
import java.util.List;

/**
 * @author yanghuaxu
 * @date 2025/6/19 13:12
 */
@Service
@Slf4j
public class ImageGenerationBiz {

    private final RestTemplate restTemplate;
    private final ObjectMapper objectMapper = new ObjectMapper();

    @Value("${image.generator.api-url}")
    private String apiUrl;

    @Value("${image.generator.api-key}")
    private String apiKey;

    @Value("${image.generator.model}")
    private String model;

    @Value("${image.generator.image-size}")
    private String imageSize;

    @Value("${image.generator.batch-size}")
    private Integer batchSize;

    // 通过构造函数注入RestTemplate Bean
    @Autowired
    public ImageGenerationBiz(RestTemplate restTemplate) {
        this.restTemplate = restTemplate;
    }

    /**
     * 生成图片的URL
     *
     * @param prompt 诗歌描述
     * @return 图片URL，失败返回空字符串
     */
    public ImageResult generateImage(String prompt) {
        // 1. 构建请求URL和头部
        HttpHeaders headers = new HttpHeaders();
        headers.set("Authorization", this.apiKey);
        headers.setContentType(MediaType.APPLICATION_JSON);

        // 2. 构建请求体
        ImageRequest requestBody = new ImageRequest();
        requestBody.setModel(this.model);
        requestBody.setImageSize(this.imageSize);
        requestBody.setBatchSize(this.batchSize);
        requestBody.setPrompt(prompt);

        // 3. 创建请求实体
        HttpEntity<ImageRequest> requestEntity = new HttpEntity<>(requestBody, headers);

        try {
            // 4. 发送POST请求
            ResponseEntity<ImageResponse> response = restTemplate.exchange(
                    this.apiUrl,
                    HttpMethod.POST,
                    requestEntity,
                    ImageResponse.class
            );

            // 5. 处理响应
            if (response.getStatusCode() == HttpStatus.OK &&
                    response.getBody() != null &&
                    response.getBody().getImages() != null &&
                    !response.getBody().getImages().isEmpty()) {

                String imageUrl = response.getBody().getImages().get(0).getUrl();
                String base64Data = downloadImageAsBase64(imageUrl);

                return new ImageResult(imageUrl, base64Data);
            }
        } catch (Exception e) {
            e.printStackTrace();
            // 捕获所有异常（网络问题、JSON解析异常等）
            System.err.println("Error generating image: " + e.getMessage());
        }

        // 6. 任何异常情况返回空字符串
        return new ImageResult("", "");
    }

    public String downloadImageAsBase64(String signedUrl) {
        try {
            // 避免 URL 被二次编码
            String decodedUrl = URLDecoder.decode(signedUrl, "UTF-8");

            // 推荐使用 HttpComponentsClientHttpRequestFactory 避免一些 header 问题
            RestTemplate restTemplate = new RestTemplate(new HttpComponentsClientHttpRequestFactory());

            ResponseEntity<byte[]> response = restTemplate.getForEntity(decodedUrl, byte[].class);

            if (response.getStatusCode().is2xxSuccessful() && response.getBody() != null) {
                byte[] imageBytes = response.getBody();
                log.info("原始图片大小: {} KB", imageBytes.length / 1024.0);
                String mimeType = "image/jpeg";
                byte[] compressedBytes = compressPng(imageBytes);
                String base64 = Base64.getEncoder().encodeToString(compressedBytes);
                log.info("压缩后图片大小: {} KB", compressedBytes.length / 1024.0);
                return "data:" + mimeType + ";base64," + base64;
            } else {
                throw new RuntimeException("Image download failed: HTTP " + response.getStatusCode());
            }
        } catch (Exception e) {
            throw new RuntimeException("Error downloading image: " + e.getMessage(), e);
        }
    }

    private byte[] compressPng(byte[] original) throws IOException {
        ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
        Thumbnails.of(new ByteArrayInputStream(original))
                .scale(1.0) // 保持原始尺寸
                .outputQuality(0.7f) // 压缩质量 (0-1)
                .outputFormat("jpg") // 保持PNG格式
                .toOutputStream(outputStream);

        return outputStream.toByteArray();
    }

    private String getMimeTypeFromUrl(String url) {
        if (url.endsWith(".png")) {
            return "image/png";
        } else if (url.endsWith(".jpg") || url.endsWith(".jpeg")) {
            return "image/jpeg";
        } else if (url.endsWith(".gif")) {
            return "image/gif";
        }
        // 默认 MIME 类型
        return "application/octet-stream";
    }

    @Data
    static class ImageRequest {
        private String model;
        private String imageSize;
        private int batchSize;
        private String prompt;
    }

    @Data
    public static class ImageResult {
        private String url;
        private String base64;

        public ImageResult(String url, String base64) {
            this.url = url;
            this.base64 = base64;
        }
    }

    @Data
    static class ImageResponse {
        private List<ImageItem> images;
    }

    @Data
    static class ImageItem {
        private String url;
    }

}
